package com.ahnu.tongue.utils;

import com.ahnu.tongue.common.BusinessException;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.Arrays;
import java.util.UUID;

@Slf4j
@Component
public class FileUtils {

    @Value("${file.upload-dir}")
    private String uploadDir;

    @Value("${file.allowed-types}")
    private String allowedTypes;

    @Value("${file.max-size}")
    private long maxSize;

    /**
     * 上传图片
     * @param file 图片文件
     * @return 图片URL（相对路径）
     * @throws BusinessException 当上传失败时
     */
    public String uploadImage(MultipartFile file) {
        if (file == null || file.isEmpty()) {
            throw new BusinessException("请选择要上传的图片");
        }

        // 检查文件类型
        String contentType = file.getContentType();
        if (contentType == null || !contentType.startsWith("image/")) {
            throw new BusinessException("只支持图片文件上传");
        }

        String extension = StringUtils.getFilenameExtension(file.getOriginalFilename());
        if (extension == null || !isAllowedFileType(extension)) {
            throw new BusinessException("不支持的图片格式，允许的格式：" + allowedTypes);
        }

        // 检查文件大小
        if (file.getSize() > maxSize) {
            throw new BusinessException(String.format("图片大小超过限制（最大%dMB）", maxSize / (1024 * 1024)));
        }

        try {
            // 创建上传目录
            Path uploadPath = Paths.get(uploadDir);
            if (!Files.exists(uploadPath)) {
                Files.createDirectories(uploadPath);
            }

            // 生成文件名
            String fileName = generateFileName(extension);
            Path filePath = uploadPath.resolve(fileName);

            // 保存文件
            file.transferTo(filePath.toFile());
            log.info("图片上传成功：{}", fileName);

            return fileName;
        } catch (IOException e) {
            log.error("图片上传失败", e);
            throw new BusinessException("图片上传失败");
        }
    }

    /**
     * 删除图片
     * @param imageUrl 图片URL（相对路径）
     */
    public void deleteImage(String imageUrl) {
        if (!StringUtils.hasText(imageUrl)) {
            return;
        }

        try {
            Path imagePath = Paths.get(uploadDir, imageUrl);
            if (Files.deleteIfExists(imagePath)) {
                log.info("图片删除成功：{}", imageUrl);
            }
        } catch (IOException e) {
            log.error("删除图片失败: {}", imageUrl, e);
        }
    }

    /**
     * 获取文件的绝对路径
     * @param relativePath 相对路径
     * @return 绝对路径
     * @throws BusinessException 当路径为空或无效时
     */
    public String getAbsolutePath(String relativePath) {
        if (!StringUtils.hasText(relativePath)) {
            throw new BusinessException("文件路径不能为空");
        }

        // 处理以 /upload/ 开头的路径
        if (relativePath.startsWith("/upload/")) {
            relativePath = relativePath.substring("/upload/".length());
        }

        // 验证文件是否存在
        Path path = Paths.get(uploadDir, relativePath);
        if (!Files.exists(path)) {
            throw new BusinessException("文件不存在：" + relativePath);
        }

        return path.toString();
    }

    /**
     * 检查文件类型是否允许
     */
    private boolean isAllowedFileType(String extension) {
        return Arrays.asList(allowedTypes.split(","))
                .contains(extension.toLowerCase());
    }

    /**
     * 生成唯一的文件名
     */
    private String generateFileName(String extension) {
        return UUID.randomUUID().toString() + "." + extension;
    }
} 